/*********************************************************************
* File: ICombat.h
*
* Supports agent combat behavior.
*********************************************************************/
#pragma once

#include "../globals.h"

namespace agents{namespace interfaces{
	/**
	* \class ICombat
	* \brief Supports agent combat behavior.
	*
	* Defines actuators, sensors and beliefs relevant for agent
	* combat behavior.
	*
	* \author Instituto Superior Tecnico de Lisboa, Portugal
	* \author Technical University of Lisbon, Portugal
	* 
	* \author Agentes Autonomos e Sistemas Multiagente
	* \author Autonomous Agents and Multiagent Systems
	* 
	* \version	1.0
	* \date		2006/2007
	**/
	class ICombat
	{
	public:
		/**
		* \brief Minimum distance to be able to defuse the bomb.
		**/
		static const float sufficientDistanceToDefuseBomb;

		/**
		* \brief Whether the agent has a specific weapon.
		* 
		* \param[in] name The weapon name.
		**/
		virtual bool hasWeapon(char* name) = 0;
		/**
		* \brief Whether the agent has a specific weapon.
		*
		* \param[in] id The weapon id.
		**/
		virtual bool hasWeapon(WeaponIds::Enumeration id) = 0;
		/**
		* \brief Whether the agent is carrying a primary weapon.
		*
		* Primary weapons include shotguns, SMGs, rifles and machine guns. 
		**/
		virtual bool hasPrimaryWeapon() = 0;
		/**
		* \brief Whether the agent is carrying a secondary weapon.
		*
		* Secondary weapons include pistols.
		**/
		virtual bool hasSecondaryWeapon() = 0;
		/**
		* \brief Whether the agent is carrying the bomb (C4).
		**/
		virtual bool hasBomb() = 0;
		/** 
		* \brief Whether the agent is in a bomb site. 
		**/
		virtual bool isInBombSite() = 0;
		/**
		* \brief The agent's armour. 
		*
		* The agent is considered to have armour if it has a vest or helmet.
		**/
		virtual int armour() = 0;
		/**
		* \brief Gets the primary weapon id. 
		**/
		virtual WeaponIds::Enumeration getPrimaryWeaponId() = 0;
		/**
		* \brief Gets the secondary weapon id.
		**/
		virtual WeaponIds::Enumeration getSecondaryWeaponId() = 0;
		/**
		* \brief Gets the current weapon id.
		*
		* The current weapon is the one which is selected and can be
		* a primary or secondary weapon.
		**/
		virtual WeaponIds::Enumeration getCurrentWeapon() = 0;
		/**
		* \brief Gets the ammo for the current weapon.
		**/
		virtual int getAmmo(void) = 0;
		/**
		* \brief Gets the ammo in clip for the current weapon.
		**/
		virtual int getAmmoInClip(void) = 0;

		/**
		* \brief Triggers the current weapon's primary attack.
		*
		* Besides the primary attack, some weapons have a secondary 
		* attack (see #secondaryAttack)
		**/
		virtual void primaryAttack() = 0;
		/**
		* \brief Triggers the current weapon's secondary attack.
		**/
		virtual void secondaryAttack() = 0;
		/**
		* \brief Reloads the current weapon.
		**/
		virtual void reloadWeapon() = 0;
		/**
		* \brief Plants the bomb.
		*
		* Only works for the terrorist carrying the bomb (see #hasBomb)
		**/
		virtual bool plantBomb() = 0;
		/**
		* \brief Defuses the bomb.
		*
		* Only works for counter-terrorists and if the agent is close
		* to the bomb while looking at it. Should be invoked continuously 
		* until #hasBomb returns false.
		**/
		virtual void defuseBomb() = 0;
		/**
		* \brief Selects a weapon.
		*
		* Only works if the agent has the weapon. Should be invoked continuously 
		* until bomb is defused.
		*
		* \param[in] name The weapon name.
		**/
		virtual void selectWeapon(char* name) = 0;
		/**
		* \brief Selects a weapon.
		*
		* Only works if the agent has the weapon.
		*
		* \param[in] name The weapon id.
		**/
		virtual void selectWeapon(WeaponIds::Enumeration id) = 0;
		/**
		* \brief Selects the primary weapon.
		*
		* Only works if the agent has a primary weapon.
		**/
		virtual void selectPrimaryWeapon() = 0;
		/**
		* \brief Selects the secondary weapon.
		*
		* Only works if the agent has a secondary weapon.
		**/
		virtual void selectSecondaryWeapon() = 0;
		/**
		* \brief Drops the current weapon.
		**/
		virtual void drop() = 0;

		/**
		* \brief Gets the agent's gun position.
		**/
		virtual Vector getGunPosition() = 0;
		/**
		* \brief Gets the agent's aiming angles.
		*
		* The aiming angles define firing direction. Notice, aiming angles 
		* are different from the moving angles. 
		*
		* \return The agent's aiming angles.
		**/
		virtual Vector getAngles() = 0;
		/**
		* \brief The aim to the left actuator.
		*
		* Makes the agent aim towards the left. Notice, the actuator must be
		* invoked at every cycle for continuous rotation.
		* Does not affect the moving angles (see agents::interfaces::INavigation).
		**/
		virtual void aimLeft() = 0;
		/**
		* \brief The aim to the right actuator.
		*
		* Makes the agent aim towards the right. Notice, the actuator must be
		* invoked at every cycle for continuous rotation
		* Does not affect the moving angles (see agents::interfaces::INavigation).
		**/
		virtual void aimRight() = 0;
		/**
		* \brief The aim upwards actuator.
		*
		* Makes the agent aim upwards. Notice, the actuator must be
		* invoked at every cycle for continuous rotation.
		* Does not affect the moving angles (see agents::interfaces::INavigation).
		**/
		virtual void aimUp() = 0;
		/**
		* \brief The aim downards actuator.
		*
		* Makes the agent aim downwards. Notice, the actuator must be
		* invoked at every cycle for continuous rotation.
		* Does not affect the moving angles (see agents::interfaces::INavigation).
		**/
		virtual void aimDown() = 0;
		/**
		* \brief Makes the agent aim at a specific target.
		*
		* Notice, the actuator must be invoked at every cycle for continuous rotation.
		* Does not affect the moving angles (see agents::interfaces::INavigation).
		*
		* \param[in] target The target.
		**/
		virtual void aimAt(Vector target) = 0;
		/**
		* \brief Whether the agent is aiming in the direction of a target.
		*
		* \param[in] target The target.
		**/
		virtual bool isAimingAt(Vector target) = 0;

		/**
		* \brief Gets information about a weapon.
		*
		* \param[in] id The weapon id.
		*
		* \return The weapon info.
		**/
		virtual WeaponInfo* getWeaponInfo(WeaponIds::Enumeration id) = 0;
	};
}}
